/**
 *  Allows to communicate with server by using native XHR object
 *  Follow next convention about CRUD operations:
 *      get -       GET http method, returns entity or array of entities
 *      create -    POST http method, data is a entity or arrau of entities to create, returns id or array or ids for created entities
 *      update -    PUT http method
 *      delete -    DELETE http method
 * @type {Object}
 */

var ajax = {


    /**
     * Options:
     *
     * url {String} - URL to make request
     * data {Object|Array} - data which we send to server
     * params {Object} - URI query parameters
     *
     */

    optionsCreate : function (url, data, params) {

        var _options = {};

        _options.url = url || "";
        _options.data = data;
        _options.params = params || "";
        return _options;

    },

    /**
     * Cross-browser object creation request
     * @return {Object} - returns the initial object XMLHttpRequest
     */

    _XmlHttpRequest : function (){
        var xmlhttp;
        try {
           xmlhttp = new ActiveXObject("Msxml2.XMLHTTP");
        } catch (e) {
            try {
                xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
            } catch (E) {
                xmlhttp = false;
            }
        }
        if (!xmlhttp && typeof XMLHttpRequest!='undefined') {
            xmlhttp = new XMLHttpRequest();
        }
        return xmlhttp;
    },


    /**
     * Get data from server
     * @param {Object} options
     * @param {Function} callback
     */

    get: function(options, callback){

        var xmlhttp = this._XmlHttpRequest();
        xmlhttp.open( "GET" , options.url + options.params);
        xmlhttp.onreadystatechange = function() {
            if(xmlhttp.readyState == 4 && xmlhttp.status == 200) {
                var type = xmlhttp.getResponseHeader("Content-Type");
                if (type === "application/json"){
                    callback(JSON.parse(xmlhttp.responseText));
                } else {
                    callback(xmlhttp.responseText);
                }
            }
        };
        xmlhttp.send(null);

    },


    /**
     * Create data on the server
     * @param {Object} options
     * @param {Function} callback
     */

    create: function(options, callback){

        var xmlhttp = this._XmlHttpRequest();
        xmlhttp.open( "POST" , options.url + options.params);
        xmlhttp.onreadystatechange = function() {
            if(xmlhttp.readyState == 4 && xmlhttp.status == 200) {
                var type = xmlhttp.getResponseHeader("Content-Type");
                if (type === "application/json"){
                    callback(JSON.parse(xmlhttp.responseText));
                } else {
                    callback(xmlhttp.responseText);
                }
            }
        };

        xmlhttp.setRequestHeader('Content-Type', 'application/json');
        xmlhttp.send(JSON.stringify(options.data));

    },

    /**
     * Update data on server
     * @param options
     * @param callback
     */

    update: function(options, callback) {

        var xmlhttp = this._XmlHttpRequest();
        xmlhttp.open( "PUT" , options.url + options.params);
        xmlhttp.onreadystatechange = function() {
            if(xmlhttp.readyState == 4 && xmlhttp.status == 200) {
                var type = xmlhttp.getResponseHeader("Content-Type");
                if (type === "application/json"){
                    callback(JSON.parse(xmlhttp.responseText));
                } else {
                    callback(xmlhttp.responseText);
                }
            }
        };

        xmlhttp.setRequestHeader('Content-Type', 'application/json');
        xmlhttp.send(JSON.stringify(options.data));

    },

    /**
     * Remove data on server
     * Data is a id or array of ids
     * @param option
     * @param callback
     */

    remove : function(options, callback){

        var xmlhttp = this._XmlHttpRequest();
        xmlhttp.open( "DELETE" , options.url + options.params);
        xmlhttp.onreadystatechange = function() {
            if(xmlhttp.readyState == 4 && xmlhttp.status == 200) {
                var type = xmlhttp.getResponseHeader("Content-Type");
                if (type === "application/json"){
                    callback(JSON.parse(xmlhttp.responseText));
                } else {
                    callback(xmlhttp.responseText);
                }
            }
        };

        xmlhttp.setRequestHeader('Content-Type', 'application/json');
        xmlhttp.send(JSON.stringify(options.data));

    }

};
